package com.google.code.irouter.portal.server;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import org.apache.commons.lang.Validate;

import com.google.appengine.api.datastore.Key;
import com.google.appengine.api.datastore.KeyFactory;
import com.google.appengine.repackaged.com.google.common.base.StringUtil;
import com.google.code.irouter.batch.api.Sender;
import com.google.code.irouter.model.Api;
import com.google.code.irouter.model.Consumer;
import com.google.code.irouter.model.Model;
import com.google.code.irouter.portal.client.rpc.consumer.ConsumerResult;
import com.google.code.irouter.portal.client.rpc.consumer.ConsumerService;
import com.google.code.irouter.utils.ApiUtil;
import com.google.code.irouter.utils.DateTimeUtil;
import com.google.code.irouter.utils.ModelUtil;
import com.google.gwt.user.server.rpc.RemoteServiceServlet;

public class ConsumerServiceImpl extends RemoteServiceServlet implements ConsumerService {

	private static final long serialVersionUID = 966737766093675224L;

	public static String getSenderName(String id) {
		Api api = ApiUtil.get(Sender.class.getSimpleName(), id);
		return api.getName();
	}
	
	@Override
	public List<ConsumerResult> load(String tags)
			throws IllegalArgumentException {
		List<ConsumerResult> consumerResultList = null;
		try {
			List<Model> objectList = new ArrayList<Model>();
			Map<String, Object> cond = new HashMap<String, Object>();
			try{
				Validate.notEmpty(tags);
				String[] tagArray = StringUtil.trimEnd(tags).split(" ");
				List<String> tagList = Arrays.asList(tagArray);			
				cond.put("tags", tagList);
			} catch (IllegalArgumentException e) {
			}
			cond.put("owner", getThreadLocalRequest().getUserPrincipal().getName());
			objectList = ModelUtil.select(Consumer.class, cond);
			consumerResultList = new ArrayList<ConsumerResult>();
			for(Object object : objectList){
				Consumer consumer = (Consumer) object;
				ConsumerResult consumerResult = new ConsumerResult();
				consumerResult.setId(consumer.getKey().getId());
				consumerResult.setName(consumer.getName());
				consumerResult.setOwner(consumer.getOwner());
				consumerResult.setUser(consumer.getUser());
				consumerResult.setPassword(consumer.getPassword());
				consumerResult.setConsumerKey(consumer.getConsumerKey());
				consumerResult.setConsumerSecret(consumer.getConsumerSecret());
				consumerResult.setMaxLength(consumer.getMaxLength());
				consumerResult.setQuota(consumer.getQuota());
				consumerResult.setSender(getSenderName(consumer.getSender()));
				consumerResult.setCreateDate(DateTimeUtil.formatDate(consumer.getCreateDate()));
				consumerResult.setUpdateDate(DateTimeUtil.formatDate(consumer.getUpdateDate()));
				consumerResultList.add(consumerResult);
			}
		} catch (Exception exception) {
			// TODO
		}
		return consumerResultList;
	}

	@Override
	public ConsumerResult get(String id) throws IllegalArgumentException {
		List<Model> modelList = ModelUtil.select(Consumer.class, KeyFactory.createKey(Consumer.class.getSimpleName(), Long.valueOf(id)));
		ConsumerResult consumerResult = null;
		try {
			if(modelList.size() > 0) {
				consumerResult = new ConsumerResult();
				Consumer consumer = (Consumer) modelList.get(0);
				consumerResult.setId(Long.valueOf(id));
				consumerResult.setName(consumer.getName());
				consumerResult.setOwner(consumer.getOwner());
				consumerResult.setConsumerKey(consumer.getConsumerKey());
				consumerResult.setConsumerSecret(consumer.getConsumerSecret());
				consumerResult.setUser(consumer.getUser());
				consumerResult.setPassword(consumer.getPassword());
				consumerResult.setMaxLength(consumer.getMaxLength());
				consumerResult.setQuota(consumer.getQuota());
				if(consumer.getTags() != null) {
					StringBuffer stringBuffer = new StringBuffer();
					for(String tag : consumer.getTags()) {
						stringBuffer.append(tag);
						stringBuffer.append(" ");
					}
					consumerResult.setTags(StringUtil.trimEnd(stringBuffer.toString()));
				}
				consumerResult.setSender(consumer.getSender());
			}
		} catch (Exception exception) {
			// TODO
		}
		return consumerResult;
	}

	@Override
	public boolean save(String id, String name, String sender,
			String consumerKey, String consumerSecret, String user,
			String password, int maxLength, int quota, String tags)
			throws IllegalArgumentException {
		boolean result = true;
		try {
			Consumer consumer = new Consumer();
			if(id.length() > 0) {
				Key oldKey = KeyFactory.createKey(Consumer.class.getSimpleName(), Long.valueOf(id));
				consumer = (Consumer) ModelUtil.select(Consumer.class, oldKey).get(0);
			}
			List<String> tagList = new ArrayList<String>();
			try{
				Validate.notEmpty(tags);
				String[] tagArray = StringUtil.trimEnd(tags).split(" ");				
				tagList = new ArrayList<String>(Arrays.asList(tagArray));
			} catch (IllegalArgumentException e) {
			}
			consumer.setOwner(getThreadLocalRequest().getUserPrincipal().getName());
			consumer.setName(name);
			consumer.setSender(sender);
			consumer.setConsumerKey(consumerKey);
			consumer.setConsumerSecret(consumerSecret);
			consumer.setUser(user);
			consumer.setPassword(password);
			consumer.setMaxLength(maxLength);
			consumer.setQuota(quota);
			consumer.setTags(tagList);
			if(id.length() > 0) {
				consumer.pushUpdateDate();
			}
			else {
				consumer.pushCreatDate();
				consumer.setLastCount(0);
				consumer.setLastHour(DateTimeUtil.getNow());
			}
			ModelUtil.save(consumer);
		} catch (Exception exception) {
			// TODO
			result = false;
		}
		return result;
	}

	@Override
	public boolean remove(String[] ids) throws IllegalArgumentException {
		boolean result = true;
		try {
			List<Key> idList = new ArrayList<Key>();
			for(String id : ids) {
				idList.add(KeyFactory.createKey(Consumer.class.getSimpleName(), Long.valueOf(id)));
			}
			ModelUtil.remove(idList);
		} catch (Exception exception) {
			// TODO
			result = false;
		}
		return result;
	}
}
